<?php

//use phpseclib3\Net\SSH2;
use phpseclib3\Net\SFTP;

require 'vendor/autoload.php';

$config = include './config.php';

$host = $config['host'];
$username = $config['username'];
$password = $config['password'];

$logFile = $config['localDir'].'\\'.date('Y_m_d_H_i_s').'.log';
$remoteDir = $config['remoteDir'] = str_replace('\\', '/', $config['remoteDir']);
$localDir = $config['localDir'] = str_replace('\\', '/', $config['localDir']);


//$ssh = new SSH2($host);
//if (!$ssh->login($username, $password)) {
//    exit('Login Failed');
//}
$sftp = new SFTP($host);
if (!$sftp->login($username, $password)) {
    exit('SFTP Login Failed');
}

// 递归获取远程目录下的所有文件
function recursiveRemoteFiles($sftp, $remoteDir)
{
    global $config;
    global $logFile;
    $files = $sftp->nlist($remoteDir);
    foreach ($files as $file) {
        if ($file != '.' && $file != '..') {
            $remotePath = "$remoteDir/$file";
            $localPath = str_replace($config['remoteDir'], $config['localDir'], $remotePath);
            if ($sftp->is_dir($remotePath)) {
                if (!is_dir($localPath)) {
                    mkdir($localPath, 0777, true);
                }
                recursiveRemoteFiles($sftp, $remotePath);
            } else {
                // 下载备份文件到本地
                $remoteSha1 = trim($sftp->exec("sha1sum $remotePath | awk '{print $1}'"));
                if (file_exists($localPath)) {
                    $localSha1 = sha1_file($localPath);
                    if ($localSha1 == $remoteSha1) {
                        $log = $remotePath."->文件已在本地存在并且校验一致跳过备份\n";
                        //echo $log;
                        file_put_contents($logFile, $log, FILE_APPEND);
                        continue;
                    } else {
                        $log = $remotePath."->文件变更重命名本地文件后重新拉取远程文件\n";
                        $log .= 'remote file shar1 <'.$remoteSha1.'> != local file shar1 <'.$localSha1.">\n";
                        echo $log;
                        file_put_contents($logFile, $log, FILE_APPEND);
                        rename($localPath, $localPath.'.bak_'.date('YmdHis'));//远程文件已经发生变化
                    }
                }
                if ($sftp->get($remotePath, $localPath)) {
                    $log = $remotePath."->备份成功\n";
                    echo $log;
                    file_put_contents($logFile, $log, FILE_APPEND);
                } else {
                    file_put_contents($logFile, "备份失败，获取文件".$remotePath."时失败\n", FILE_APPEND);
                    die($remotePath.'备份失败');
                }
            }
        }
    }
}

file_put_contents($logFile, "开始执行\n", FILE_APPEND);
recursiveRemoteFiles($sftp, $remoteDir);
file_put_contents($logFile, "操作完成\n", FILE_APPEND);